import org.objectweb.asm.*;

/**
 * ASM字节码生成示例
 * 演示如何使用ASM库动态生成Java类
 */
public class ASMBytecodeGeneration {

    public static void main(String[] args) throws Exception {
        // 1. 创建ClassWriter，用于生成类文件
        ClassWriter cw = new ClassWriter(ClassWriter.COMPUTE_MAXS);

        // 2. 定义类的基本信息
        cw.visit(Opcodes.V11, Opcodes.ACC_PUBLIC,
                "com/example/GeneratedClass",
                null, "java/lang/Object", null);

        // 3. 生成默认构造器
        MethodVisitor mv = cw.visitMethod(
                Opcodes.ACC_PUBLIC,
                "<init>",
                "()V", null, null);
        mv.visitCode();
        mv.visitVarInsn(Opcodes.ALOAD, 0);
        mv.visitMethodInsn(Opcodes.INVOKESPECIAL,
                "java/lang/Object", "<init>", "()V", false);
        mv.visitInsn(Opcodes.RETURN);
        mv.visitMaxs(1, 1);
        mv.visitEnd();

        // 4. 生成一个简单方法
        generateMethod(cw);

        // 5. 完成类定义并获取字节码
        cw.visitEnd();
        byte[] bytecode = cw.toByteArray();

        // 6. 保存到文件或加载使用
        saveToFile(bytecode, "GeneratedClass.class");
    }

    /**
     * 生成一个简单方法：public int add(int a, int b)
     */
    private static void generateMethod(ClassWriter cw) {
        MethodVisitor mv = cw.visitMethod(
                Opcodes.ACC_PUBLIC,
                "add",
                "(II)I", null, null);
        mv.visitCode();
        mv.visitVarInsn(Opcodes.ILOAD, 1);  // 加载第一个参数
        mv.visitVarInsn(Opcodes.ILOAD, 2);  // 加载第二个参数
        mv.visitInsn(Opcodes.IADD);        // 执行加法
        mv.visitInsn(Opcodes.IRETURN);     // 返回结果
        mv.visitMaxs(2, 3);                // 栈和局部变量表大小
        mv.visitEnd();
    }

    /**
     * 将字节码保存到文件
     */
    private static void saveToFile(byte[] bytecode, String filename) {
        try (FileOutputStream fos = new FileOutputStream(filename)) {
            fos.write(bytecode);
        } catch (IOException e) {
            e.printStackTrace();
        }
    }
}
